import React, { useEffect, useMemo, useState } from "react";
import { Button, Input, message, Modal, Tree, Typography } from "antd";
import { DeleteOutlined, PlusOutlined } from "@ant-design/icons";
import debounce from "lodash/debounce";

import request from "@/utils/request";
// import AddModal from './AddModal'
import { useAppSelector } from "@/utils/hooks";
import { getAllParentIds, plainTree, transformResourceTree } from "@/utils/util";

import { RecordDetail } from "../type";
import AddModal from "./AddModal";

interface Props {
	editDetail?: RecordDetail;
	onSelect: (keys:  React.Key) => void;
}

const getFirstRole = (roleList: ResourceNode[]): ResourceNode => {
	const walk = (roleList: ResourceNode[]): ResourceNode | undefined => {
		for (let i = 0; i < roleList.length; i++) {
			const item = roleList[i];
			if (item.parentId) {
				return item;
			} else if (item.children) {
				return walk(item.children);
			}
		}
	};
	return walk(roleList) as ResourceNode;
};

const ResourceSide: React.FC<Props> = ({ onSelect, editDetail }) => {
	const [app] = useAppSelector(state => [state.app]);

	const [addOpen, setAddOpen] = useState(false);
	const [treeList, setTreeList] = useState<ResourceNode[]>([]);
	const [searchVal, setSearchVal] = useState("");
	const [selectedKeys, setSelectedKeys] = useState<React.Key[]>();
	const [expandedKeys, setExpandedKeys] = useState<React.Key[]>([]);
	const [curResourceNode, setCurResourceNode] = useState<ResourceNode>();
	const [autoExpandParent, setAutoExpandParent] = useState(true);

	useEffect(() => {
		queryResourceList();
	}, [editDetail, app.currentEntity]);

	const queryResourceList = () => {
		const data = { tenantId: app.currentEntity.entityId };
		request("resourceTree", { data }).then(res => {
			if (res.code === 0 && res.data) {
				const transedTreeList = res.data
				setTreeList(transedTreeList);
				const firstRole = transedTreeList[0];
				setExpandedKeys([...expandedKeys, firstRole?.parentId as React.Key]);
				handleSelect([firstRole.key!]);
			}
		});
	};

	const handleAddClick = () => {
		setAddOpen(true);
	};

	const plainedList = useMemo(() => {
		return plainTree(treeList);
	}, [treeList]);

	const handleInputChange = debounce((e: React.ChangeEvent<HTMLInputElement>) => {
		const value = e.target.value;
		const nodeKeys = plainedList
			.map(item => {
				if ((item.title as string).indexOf(value) > -1) {
					return item.key;
				}
				return null;
			})
			.filter((item, i, self) => item && self.indexOf(item) === i);

		const newExpandedKeys = getAllParentIds(treeList, nodeKeys as React.Key[]);
		setExpandedKeys(newExpandedKeys as React.Key[]);
		setSearchVal(value);
		setAutoExpandParent(true);
	}, 300);

	const treeData = useMemo(() => {
		const loop = (data: ResourceNode[]): ResourceNode[] =>
			data.map(item => {
				const strTitle = item.title as string;
				const index = strTitle.indexOf(searchVal);
				const beforeStr = strTitle.substring(0, index);
				const afterStr = strTitle.slice(index + searchVal.length);
				const title: any =
					index > -1 ? (
						<span>
							{beforeStr}
							<span className="site-tree-search-value">{searchVal}</span>
							{afterStr}
						</span>
					) : (
						<span>{strTitle}</span>
					);
				if (item.children) {
					return { ...item, title, key: item.key, children: loop(item.children) };
				}
				return {
					...item,
					title,
					key: item.key
				};
			});
		return loop(treeList);
	}, [searchVal, treeList]);

	const remove = (nodeData: ResourceNode) => {
		Modal.confirm({
			title: "提示",
			content: `是否将${nodeData.title}资源点删除？`,
			onOk() {
				return request("resourceManageDelete", {
					data: {
						id: nodeData.id
					}
				}).then(res => {
					if (res.code === 0) {
						message.success("删除成功");
						queryResourceList();
					}
				});
			}
		});
	};

	const renderTitle = (nodeData: ResourceNode) => {
		return (
			<div className="betweenCenter">
				<span>{nodeData.title}</span>
				{!nodeData.status && (
					<span className="ml20" onClick={() => remove(nodeData)}>
						<DeleteOutlined></DeleteOutlined>
					</span>
				)}
			</div>
		);
	};

	const handleSelect = (selectedKeys: React.Key[], info?: { node: ResourceNode }) => {
		setSelectedKeys(selectedKeys);
		onSelect(selectedKeys[0]);
		setCurResourceNode(info?.node);
	};

	const handleExpand = (newExpandedKeys: React.Key[]) => {
		setExpandedKeys(newExpandedKeys);
		setAutoExpandParent(false);
	};

	const resourceTreeDrop = (info:any) => {
		const dropKey = info.node.key;
		const dragKey = info.dragNode.key;
		request("resourceManageEdit", {
			data: {
				id: dragKey,
				parentId: dropKey
			}
		}).then(res => {
			if (res.code === 0) {
				message.success("修改成功").then(r => r);
				queryResourceList();
			}
		});

	}

	return (
		<div className="role-manage-sider">
			<div className="betweenCenter mb20">
				<Typography.Title level={5} style={{ margin: 0 }}>
					资源列表
				</Typography.Title>
				<Button icon={<PlusOutlined />} onClick={handleAddClick}>
					添加资源
				</Button>
			</div>
			<Input.Search allowClear style={{ marginBottom: 8 }} placeholder="请输入资源名称" onChange={handleInputChange} />
			{!!treeData.length && (
				<Tree
					blockNode
					// defaultExpandAll
					className="role-manage-sider-tree mt5 breakWord"
					draggable
					onDrop={resourceTreeDrop}
					autoExpandParent={autoExpandParent}
					expandedKeys={expandedKeys}
					onExpand={handleExpand}
					selectedKeys={selectedKeys}
					onSelect={handleSelect}
					titleRender={renderTitle}
					treeData={treeData}
				/>
			)}

			<AddModal record={curResourceNode} open={addOpen} onCancel={() => setAddOpen(false)} onSearch={queryResourceList}></AddModal>
		</div>
	);
};

export default ResourceSide;
